﻿namespace EyeOpen.Windows.Form
{
	using System;
	using System.Collections.Generic;
	using System.IO;
	using System.Linq;
	using System.Runtime.Serialization;
	using System.Windows.Forms;
	using System.Xml;
	using EyeOpen.Linq;

	public class XmlFormSerializer
	{
		private readonly Type controlListType = typeof(List<ControlSerialized>);

		private readonly IContainer container;

		public XmlFormSerializer(IContainer container)
		{
			this.container = container;
		}

		public void Save(Control control, string fileName)
		{
			var controlSerializedList =
				new FormSerializer(container)
					.Save(control)
					.ToList();

			using (var stream = File.Open(fileName, FileMode.Create, FileAccess.Write))
			{
				using (var xmlWriter = new XmlTextWriter(stream, null))
				{
					xmlWriter.Formatting = Formatting.Indented;

					var serializer = new DataContractSerializer(controlListType);
					serializer.WriteObject(xmlWriter, controlSerializedList);
				}
			}
		}

		public void Load(Control control, string fileName)
		{
			IEnumerable<ControlSerialized> controlSerializedList;

			using (var stream = File.Open(fileName, FileMode.Open))
			{
				var serializer = new DataContractSerializer(controlListType);
					controlSerializedList = 
						(IEnumerable<ControlSerialized>)
							serializer
								.ReadObject(stream);
			}

			var controls = 
				control
					.Controls
					.OfType<Control>()
					.Traverse(c => c.Controls.OfType<Control>());

			foreach (var child in controls)
			{
				var child1 = child;

				var objectSerialized =
					controlSerializedList
						.Where(o => o.ControlId == child1.GetHierarchicalId())
						.SingleOrDefault();

				if (objectSerialized == null)
				{
					continue;
				}

				container
					.Resolve<IObjectSerializer>(child)
					.Load(child, objectSerialized);
			}
		}
	}
}